﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace HeresyManager.Traits
{
    [Serializable]
    public class SanctionedPsyker : Trait
    {
        int years;

        SideEffects sideeffect;

        public override string Name
        {
            get { return "Sanctioned Psyker"; }
        }


        public override IEnumerator<Comunication.Comunicator> Accire(Character c)
        {
            var e = base.Accire(c);
            while (e.MoveNext())
                yield return e.Current;

            var com = new Comunication.RoleDice("Ageing", new DiceCollection(Dice.D10, Dice.D10, Dice.D10));
            while (com.Value == -1)
                yield return com;
            years = com.Value;

            var side = new Comunication.ChooseOne<SideEffects>("Sanctioning Side Effects", new ReconstructedSkull(), new Hounted(), new UnlovleyMemories(), new TheHorror(), new PainThroughNerveInduction(), new DentalProbes(), new OpticalRupture(), new ScreamingDevotions(), new Irradience(), new TounguBound(), new ThroneWed(), new WitchPrickling(), new HypnoDoctrination());
            while (side.SelectedValue == null)
                yield return side;
            sideeffect = side.SelectedValue;

            var en = sideeffect.Accire(c);
            while (en.MoveNext())
                yield return en.Current;


            c.Age += years;

        }

        public override void DeAccire(Character c)
        {
            base.DeAccire(c);
            c.Age -= years;
            sideeffect.DeAccire(c);

        }

        #region Sideeffects
        [Serializable]
        internal abstract class SideEffects : IMinMaxRole
        {
            public abstract string Name { get; }

            public abstract int MinRole { get; }

            public virtual IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                if (false)
                    yield return null;
            }

            public virtual void DeAccire(Character c)
            {

            }

            public abstract int MaxRole { get; }
            public override string ToString()
            {
                return Name;
            }
        }
        [Serializable]
        private class ReconstructedSkull : SideEffects
        {
            int throneGeld;

            public override string Name
            {
                get { return "Reconstructed Skull"; }
            }

            public override int MinRole
            {
                get { return 1; }
            }

            public override int MaxRole
            {
                get { return 8; }
            }

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;
                c.Int -= 3;

                var dice = new Comunication.RoleDice("Throne Gelt in compensation", new DiceMultiplier(Dice.D10, 5));
                while (dice.Value == -1)
                    yield return dice;
                throneGeld = dice.Value;
                c.ThronGeld += throneGeld;

            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.Int += 3;
                c.ThronGeld -= throneGeld;
            }

        }
        [Serializable]
        private class Hounted : SideEffects
        {


            public override string Name
            {
                get { return "Hounted"; }
            }

            public override int MinRole
            {
                get { return 9; }
            }

            public override int MaxRole
            {
                get { return 14; }
            }

            int insanety;

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;

                var dice = new Comunication.RoleDice("Insanety", Dice.D10);
                while (dice.Value == -1)
                    yield return dice;
                insanety = dice.Value;
                c.InsanityPoints += insanety;

            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.InsanityPoints -= insanety;
            }


        }
        [Serializable]
        private class UnlovleyMemories : SideEffects
        {
            public override string Name
            {
                get { return "Unlovley Memories"; }
            }

            public override int MinRole
            {
                get { return 15; }
            }

            public override int MaxRole
            {
                get { return 25; }
            }
            int insanety;

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;

                var dice = new Comunication.RoleDice("Insanety", Dice.D5);
                while (dice.Value == -1)
                    yield return dice;
                insanety = dice.Value;
                c.InsanityPoints += insanety;

            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.InsanityPoints -= insanety;
            }

        }
        [Serializable]
        private class TheHorror : SideEffects
        {
            public override string Name
            {
                get { return "The Horror, The Horror"; }
            }

            public override int MinRole
            {
                get { return 26; }
            }

            public override int MaxRole
            {
                get { return 35; }
            }

            int insanety;

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;

                var dice = new Comunication.RoleDice("Insanety", Dice.D5);
                while (dice.Value == -1)
                    yield return dice;
                insanety = dice.Value;
                c.InsanityPoints += insanety;

            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.InsanityPoints -= insanety;
            }
        }
        [Serializable]
        private class PainThroughNerveInduction : SideEffects
        {
            public override string Name
            {
                get { return "Pain through Nerve Induction"; }
            }

            public override int MinRole
            {
                get { return 36; }
            }

            public override int MaxRole
            {
                get { return 42; }
            }
        }
        [Serializable]
        private class DentalProbes : SideEffects
        {
            public override string Name
            {
                get { return "Denntal Probs"; }
            }

            public override int MinRole
            {
                get { return 43; }
            }

            public override int MaxRole
            {
                get { return 49; }
            }
        }
        [Serializable]
        private class OpticalRupture : SideEffects
        {
            public override string Name
            {
                get { return "Optical Rupture"; }
            }

            public override int MinRole
            {
                get { return 50; }
            }

            public override int MaxRole
            {
                get { return 57; }
            }
        }
        [Serializable]
        private class ScreamingDevotions : SideEffects
        {
            public override string Name
            {
                get { return "Screaminf Devotions"; }
            }

            public override int MinRole
            {
                get { return 58; }
            }

            public override int MaxRole
            {
                get { return 63; }
            }
        }
        [Serializable]
        private class Irradience : SideEffects
        {
            public override string Name
            {
                get { return "Irradience"; }
            }

            public override int MinRole
            {
                get { return 64; }
            }

            public override int MaxRole
            {
                get { return 70; }
            }
        }
        [Serializable]
        private class TounguBound : SideEffects
        {
            public override string Name
            {
                get { return "Toungu Bound"; }
            }

            public override int MinRole
            {
                get { return 71; }
            }

            public override int MaxRole
            {
                get { return 75; }
            }
        }
        [Serializable]
        private class ThroneWed : SideEffects
        {
            public override string Name
            {
                get { return "Throne Wed"; }
            }

            public override int MinRole
            {
                get { return 76; }
            }

            public override int MaxRole
            {
                get { return 88; }
            }

            Talents.ChemGeld chem;

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;

                var dice = new Comunication.RoleDice("Insanety", Dice.D5);
                while (dice.Value == -1)
                    yield return dice;
                chem = new Talents.ChemGeld();

                en = c.AddTalent(chem, this);
                while (en.MoveNext())
                    yield return en.Current;

            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.RemoveTalent(chem, this);
            }
        }
        [Serializable]
        private class WitchPrickling : SideEffects
        {
            public override string Name
            {
                get { return "Witch Prickling"; }
            }

            public override int MinRole
            {
                get { return 89; }
            }

            public override int MaxRole
            {
                get { return 94; }
            }

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;
                c.T += 3;
            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.T -= 3;
            }

        }
        [Serializable]
        private class HypnoDoctrination : SideEffects
        {
            public override string Name
            {
                get { return "Hypo-doctrination"; }
            }

            public override int MinRole
            {
                get { return 95; }
            }

            public override int MaxRole
            {
                get { return 100; }
            }

            public override IEnumerator<Comunication.Comunicator> Accire(Character c)
            {
                var en = base.Accire(c);
                while (en.MoveNext())
                    yield return en.Current;
                c.Wp += 3;
            }

            public override void DeAccire(Character c)
            {
                base.DeAccire(c);
                c.Wp -= 3;
            }

        }
        #endregion


    }
}
